package com.meilai.project.job;

import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.meilai.project.constant.MaintenanceStaffChangeEnum;
import com.meilai.project.constant.MessageCenterTypeEnum;
import com.meilai.project.entity.business.customer.CustomerFollow;
import com.meilai.project.entity.business.customer.CustomerInfo;
import com.meilai.project.entity.business.workbench.CustomerEstimateRecord;
import com.meilai.project.entity.business.workbench.YearWeek;
import com.meilai.project.entity.system.Config;
import com.meilai.project.entity.system.MessageCenter;
import com.meilai.project.service.business.customer.CustomerFollowService;
import com.meilai.project.service.business.customer.CustomerInfoService;
import com.meilai.project.service.business.workbench.CustomerEstimateRecordService;
import com.meilai.project.service.business.workbench.YearWeekService;
import com.meilai.project.service.system.ConfigService;
import com.meilai.project.service.system.MessageCenterService;
import com.meilai.project.vo.business.customer.CustomerInfoScheduledJobVO;
import org.apache.commons.collections4.CollectionUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.*;
import java.util.stream.Collectors;

/**
 * 客户跟进提醒
 */
@Component
public class CustomerFollowReminderJob {
    @Autowired
    private CustomerInfoService customerInfoService;

    @Autowired
    private CustomerFollowService customerFollowService;

    @Autowired
    private MessageCenterService messageCenterService;

    @Autowired
    private CustomerEstimateRecordService customerEstimateRecordService;

    @Autowired
    private YearWeekService yearWeekService;

    @Autowired
    private ConfigService configService;

    /**
     * 每天早晨六点发送消息到消息中心提醒用户有客户临近预估签单时间但是未拜访
     */
    @Scheduled(cron = "0 0 6 * * ?")
    @Transactional(rollbackFor = Exception.class)
    public void reminder() {
        List<CustomerInfo> list = customerInfoService.list(Wrappers.<CustomerInfo>lambdaQuery().isNull(CustomerInfo::getDeleted_at).isNotNull(CustomerInfo::getMaintenance_staff_id));
        LocalDate now = LocalDate.now();
        if (CollectionUtils.isNotEmpty(list)) {
            // 获取超时配置
            Config config = configService.configDetail("reminder_time");
            int day = Integer.parseInt(config.getParams());
            List<Long> customer_ids = list.stream().map(CustomerInfo::getId).collect(Collectors.toList());
            // 查询每个客户最新的签约预估
            List<CustomerEstimateRecord> customerEstimateRecordList = customerEstimateRecordService.list(Wrappers.<CustomerEstimateRecord>lambdaQuery().in(CustomerEstimateRecord::getCustomer_id, customer_ids));
            if (CollectionUtils.isNotEmpty(customerEstimateRecordList)) {
                List<MessageCenter> messageCenterList = new ArrayList<>();
                // 查询每个客户最新的跟进时间
                Map<Long, List<CustomerFollow>> follow_map = customerFollowService.queryLatestRecord(customer_ids).stream().collect(Collectors.groupingBy(CustomerFollow::getCustomer_id));
                Set<Long> week_ids = customerEstimateRecordList.stream().map(CustomerEstimateRecord::getWeek_id).collect(Collectors.toSet());
                Map<Long, List<YearWeek>> week_map = yearWeekService.listByIds(week_ids).stream().collect(Collectors.groupingBy(YearWeek::getId));
                Map<Long, List<CustomerEstimateRecord>> estimate_record_map = customerEstimateRecordList.stream().collect(Collectors.groupingBy(CustomerEstimateRecord::getCustomer_id));
                list.forEach(customer -> {
                    // 获取最新的签约预估
                    if (estimate_record_map.containsKey(customer.getId())) {
                        List<CustomerEstimateRecord> collect = estimate_record_map.get(customer.getId()).stream().sorted(Comparator.comparing(CustomerEstimateRecord::getId).reversed()).collect(Collectors.toList());
                        // 最新的签约预估
                        CustomerEstimateRecord record = collect.get(0);
                        // 获取签约开始时间
                        if (week_map.containsKey(record.getWeek_id())) {
                            YearWeek week = week_map.get(record.getWeek_id()).get(0);
                            // 如果今天是签约开始时间
                            if (now.equals(week.getBegin_date())) {
                                // 获取最新的拜访记录
                                if (follow_map.containsKey(customer.getId())) {
                                    CustomerFollow follow = follow_map.get(customer.getId()).get(0);
                                    // 如果最近的拜访时间是预估签单时间30天之前
                                    if (follow.getFollow_time().plusDays(day).isBefore(week.getBegin_date())) {
                                        MessageCenter messageCenter = new MessageCenter();
                                        messageCenter.setType(MessageCenterTypeEnum.TIP.getType());
                                        messageCenter.setTitle("添加跟进提醒");
                                        messageCenter.setContent(customer.getName() + "签约预估的开始时间已到，但是您最近" + config.getParams() + "天都没有跟进记录，请尽快添加跟进记录");
                                        messageCenter.setUser_id(customer.getMaintenance_staff_id());
                                        messageCenter.setCreated_at(LocalDateTime.now());
                                        messageCenterList.add(messageCenter);
                                    }
                                } else {
                                    // 没有跟进记录就提醒
                                    MessageCenter messageCenter = new MessageCenter();
                                    messageCenter.setType(MessageCenterTypeEnum.TIP.getType());
                                    messageCenter.setTitle("添加跟进提醒");
                                    messageCenter.setContent(customer.getName() + "签约预估的开始时间已到，但是您最近" + config.getParams() + "天都没有跟进记录，请尽快添加跟进记录");
                                    messageCenter.setUser_id(customer.getMaintenance_staff_id());
                                    messageCenter.setCreated_at(LocalDateTime.now());
                                    messageCenterList.add(messageCenter);
                                }
                            }
                        }
                    }
                });
                messageCenterService.saveBatch(messageCenterList);
            }
        }
    }


    /**
     * 每天早晨六点发送消息到消息中心提醒用户超时未拜访的客户
     */
    @Scheduled(cron = "0 06 20 * * ?")
    @Transactional(rollbackFor = Exception.class)
    public void followReminder() {
        List<CustomerInfoScheduledJobVO> list = customerInfoService.selectList();
        // 获取当前时间
        LocalDate now = LocalDate.now();
        if (CollectionUtils.isNotEmpty(list)) {
            List<MessageCenter> messageCenterList = new ArrayList<>();
            // 获取跟进超时配置
            Config not_follow_remind = configService.configDetail("not_follow_remind");
            // 获取主动申请跟进超时配置
            Config apply_not_follow_remind = configService.configDetail("apply_not_follow_remind");
            int not_follow_remind_day = Integer.parseInt(not_follow_remind.getParams());
            int apply_not_follow_remind_day = Integer.parseInt(apply_not_follow_remind.getParams());
            List<Long> customer_ids = list.stream().map(CustomerInfo::getId).collect(Collectors.toList());
            // 查询每个客户最新的跟进时间
            Map<Long, List<CustomerFollow>> follow_map = customerFollowService.queryLatestRecord(customer_ids).stream().collect(Collectors.groupingBy(CustomerFollow::getCustomer_id));
            // 筛选出主动申请跟进的客户
            List<CustomerInfoScheduledJobVO> apply_follow_customer_list = list.stream().filter(item -> item.getType() != null && item.getType().equals(MaintenanceStaffChangeEnum.SHENG_QING_GENG_JING_TONG_GUO.getId())).collect(Collectors.toList());
            // 处理主动申请跟进的客户超时
            apply_follow_customer_list.forEach(item -> {
                // 如果今天距离审核通过超过七天了
                if (item.getUpdate_time() != null && item.getUpdate_time().toLocalDate().plusDays(apply_not_follow_remind_day).isBefore(now)) {
                    if (follow_map.containsKey(item.getId())) {
                        LocalDate follow_time = follow_map.get(item.getId()).get(0).getFollow_time();
                        if (follow_time.isBefore(item.getUpdate_time().toLocalDate())) {
                            // 最后一次跟进在审核通过之前 发送提醒
                            MessageCenter messageCenter = new MessageCenter();
                            messageCenter.setType(MessageCenterTypeEnum.TIP.getType());
                            messageCenter.setTitle("添加跟进提醒");
                            messageCenter.setContent("您申请跟进的" + item.getName() + "超过" + (now.toEpochDay() - item.getUpdate_time().toLocalDate().toEpochDay()) + "天没有跟进了" + "请尽快拜访并添加跟进记录");
                            messageCenter.setUser_id(item.getMaintenance_staff_id());
                            messageCenter.setCreated_at(LocalDateTime.now());
                            messageCenterList.add(messageCenter);
                        }
                    } else {
                        // 没有跟进 发送提醒
                        MessageCenter messageCenter = new MessageCenter();
                        messageCenter.setType(MessageCenterTypeEnum.TIP.getType());
                        messageCenter.setTitle("添加跟进提醒");
                        messageCenter.setContent("您申请跟进的" + item.getName() + "超过" + (now.toEpochDay() - item.getUpdate_time().toLocalDate().toEpochDay()) + "天没有跟进了" + "请尽快拜访并添加跟进记录");
                        messageCenter.setUser_id(item.getMaintenance_staff_id());
                        messageCenter.setCreated_at(LocalDateTime.now());
                        messageCenterList.add(messageCenter);
                    }
                }
            });
            // 处理距离上次拜访超过配置项的客户
            list.forEach(customer -> {
                if (follow_map.containsKey(customer.getId())) {
                    LocalDate last_follow_time = follow_map.get(customer.getId()).get(0).getFollow_time();
                    if (last_follow_time.plusDays(not_follow_remind_day).isBefore(now)) {
                        // 最后一次跟进在配置项超时之前 发送提醒
                        MessageCenter messageCenter = new MessageCenter();
                        messageCenter.setType(MessageCenterTypeEnum.TIP.getType());
                        messageCenter.setTitle("添加跟进提醒");
                        messageCenter.setContent("您跟进的" + customer.getName() + "超过" + (now.toEpochDay() - last_follow_time.toEpochDay()) + "天没有跟进了" + "请尽快拜访并添加跟进记录");
                        messageCenter.setUser_id(customer.getMaintenance_staff_id());
                        messageCenter.setCreated_at(LocalDateTime.now());
                        messageCenterList.add(messageCenter);
                    }
                }
            });
            if (CollectionUtils.isNotEmpty(messageCenterList)) {
                messageCenterService.saveBatch(messageCenterList);
            }
        }
    }
}
